/**************************************************************************************
 *
 * @(#) AuthBizImpl.java
 * @Package com.jgdt.jgdtkasannong_university_gene_backend.biz.user.impl
 **************************************************************************************/
package com.jgdt.jgdtkasannong_university_gene_backend.biz.user.impl;

import cn.hutool.core.collection.CollectionUtil;
import com.jgdt.jgdtkasannong_university_gene_backend.biz.user.AuthBiz;
import com.jgdt.jgdtkasannong_university_gene_backend.common.Sysconstant;
import com.jgdt.jgdtkasannong_university_gene_backend.common.enums.SystemCodeEnums;
import com.jgdt.jgdtkasannong_university_gene_backend.common.example.custom.BusinessException;
import com.jgdt.jgdtkasannong_university_gene_backend.entity.user.SysUser;
import com.jgdt.jgdtkasannong_university_gene_backend.enums.user.EnabledEnums;
import com.jgdt.jgdtkasannong_university_gene_backend.service.user.UserService;
import com.jgdt.jgdtkasannong_university_gene_backend.utils.JwtUtils;
import com.jgdt.jgdtkasannong_university_gene_backend.utils.RedisUtils;
import com.jgdt.jgdtkasannong_university_gene_backend.vo.user.LoginVo;
import com.jgdt.jgdtkasannong_university_gene_backend.vo.user.LogoutVo;
import com.jgdt.jgdtkasannong_university_gene_backend.vo.user.RegisterVo;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * @description: 用户认证
 * @author: huangAn
 * @createDate: 2025/04/18
 */
@Service
public class AuthBizImpl implements AuthBiz {

    private final PasswordEncoder passwordEncoder;
    private final AuthenticationManager authenticationManager;
    private final JwtUtils jwtUtils;

    @Value("${jwt.redis-login-blacklist-outtime}")
    private long loginBlacklistOuttime;

    public AuthBizImpl(PasswordEncoder PasswordEncoder,AuthenticationManager authenticationManager
            ,JwtUtils jwtUtils) {
        this.passwordEncoder = PasswordEncoder;
        this.authenticationManager=authenticationManager;
        this.jwtUtils=jwtUtils;

    }
    @Autowired
    private UserService userService;
    @Autowired
    private JwtUtils jwtUtils1;
    @Autowired
    private RedisUtils redisUtils;


    @Override
    @Transactional(rollbackFor = Exception.class)
    public void register(RegisterVo registerVo) {
        //入参校验 todo
        String password =registerVo.getPassword();
        if(password.length()<6){
            throw new BusinessException(SystemCodeEnums.BAD_REQUEST.getKey(),"密码不符合规范!");
        }
        //用户校验
        userService.checkExistsUser(registerVo);
        //新增
        SysUser user = new SysUser();
        user.setUsername(registerVo.getUsername());
        user.setPassword(passwordEncoder.encode(registerVo.getPassword()));
        user.setEmail(registerVo.getEmail());
        user.setEnabled(EnabledEnums.YES.getKey());
        userService.insertUser(user);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public String login(LoginVo request) {
        Authentication authentication = authenticationManager.authenticate(
                new UsernamePasswordAuthenticationToken(request.getUsername(), request.getPassword()));

        SecurityContextHolder.getContext().setAuthentication(authentication);
        String jwt = jwtUtils1.generateToken((UserDetails) authentication.getPrincipal());
        if(StringUtils.isNotEmpty(jwt)){
            //清除 redis中对应用户黑名单信息
            redisUtils.del(Sysconstant.USER_LOGIN_BLACKLIST_KEY_USERNAME +request.getUsername());
        }
        return jwt;
    }

    @Override
    public void logout(LogoutVo request) {
        //校验是否正常用户
        SysUser sysUser=new SysUser();
        sysUser.setUsername(request.getUsername());
        List<SysUser> sysUserList=userService.queryUser(sysUser);
        if(CollectionUtil.isEmpty(sysUserList)){
            throw new BusinessException(SystemCodeEnums.BAD_REQUEST.getKey(),"该用户不存在!");
        }
        //将令牌加入黑名单
        redisUtils.set(Sysconstant.USER_LOGIN_BLACKLIST_KEY_USERNAME +request.getUsername(),request.getUsername(),loginBlacklistOuttime);
        // Token 无效或过期时，清理 SecurityContext
        SecurityContextHolder.clearContext();
    }
}




